<?php

namespace App\Service;

use App\Constants\ErrorCode;
use App\Exception\BusinessException;
use Elasticsearch\Common\Exceptions\Conflict409Exception;
use Hyperf\Elasticsearch\ClientBuilderFactory;
use Hyperf\Utils\ApplicationContext;
use Hyperf\Utils\Str;
use Hyperf\Di\Annotation\Inject;
use Psr\Container\ContainerExceptionInterface;
use Psr\Container\NotFoundExceptionInterface;

class EsService  extends EsBaseService
{
    /**
     * @Inject
     * @var ProductService
     */
    private $productService;

    /**
     * @Inject
     * @var FlyShopService
     */
    private $shopService;

    const TYPE_KEY = [1,2,3,4,5,6];
    const TYPE_VALUE = [1=>'SPU',2=>'SKU',3=>'VIDEO',4=>'SHOP',5=>'CENTER',6=>'STAR'];
    public $es_key='';
    public $es_type= 'ALL';
    public $es_data =[];
    public $id;

//    /**
//     * @param $id
//     * @param $type
//     */
//    public function __construct($id=0,$type=0)
//    {
//////        默认ALL 全部搜索
////        parent::__construct();
////        if($id&&$type){
////            $this->es_key = self::TYPE_VALUE[$type].'_'.$id;
////            $this->es_type =  self::TYPE_VALUE[$type];
////            $this->id = $id;
////        }
//        if ($type!=0&&!in_array($type,self::TYPE_KEY)){
//            throw new \RuntimeException("数据类型{$type}不符合规范！", ErrorCode::SERVER_ERROR);
//        }
//    }

    /**
     * @param $id
     * @param $type
     */
    public function set_key($id=0,$type=1)
    {
        $key = [];
        if($id&&$type){
            $key['es_key'] = self::TYPE_VALUE[$type].'_'.$id;
            $key['es_type'] = self::TYPE_VALUE[$type];
            $this->type = $key['es_type'];
            $key['eid'] = $id;
        }
        if (!in_array($type,self::TYPE_KEY)){
            throw new \RuntimeException("数据类型{$type}不符合规范！", ErrorCode::SERVER_ERROR);
        }
        return $key;
    }
    /**
     * @param int $id
     * @param int $type
     * @return bool
     */
//增加商品的方法，
//    todo 后续type增加sku  视频  商铺等
    public function es_add(int $id, int $type):bool
    {
        if (in_array($type,self::TYPE_KEY)){

            $data = [];
            switch ($type){
//               SPU 商品适配
                case 1:
                    $this->product_data($id);
                break;
                //          SHOP 商铺适配
                case 4:
                    $this->shop_data($id);
                    break;
            }
            return true;
        }else{
            throw new \RuntimeException("数据类型{$type}不符合规范！", ErrorCode::SERVER_ERROR);
        }
    }

    //更新商铺商品的方法，
    public function shop_product_add(int $shop_id, int $type=1)
    {
       $spu_list =  $this->productService->index(['shop_id'=>$shop_id],2);
       if($spu_list){
           $spu_list = $spu_list->get()->toArray();
           foreach ($spu_list as $key=>$value){
               $this->productService->es_push(intval($value['id']),intval($type));
           }
       }
    }
    //更新商铺商品的方法，
    public function shop_product_clear(int $shop_id, int $type=1)
    {
        $spu_list =  $this->productService->index(['shop_id'=>$shop_id],2);
        if($spu_list){
            $spu_list = $spu_list->get()->toArray();
            foreach ($spu_list as $key=>$value){
                $this->deleteDoc(intval($value['id']),$type);
            }
        }
    }
    public function es_info(int $id, int $type)
    {
        $key = $this->set_key($id,$type);
        return $this->select($key,[],true);
    }

    public function  product_data($id)   {
            $data = $this->productService->info(intval($id));

            $key = $this->set_key($id,1);
            if($data){
                $data = $data->toArray();
                $sku_list =$data['sku_list'];
                if($sku_list==''){
                    throw new \RuntimeException("商品没有sku,无需上架展示", ErrorCode::SERVER_ERROR);
                }
                $spec_key = array_column($data['spec_key'],'spec_name');
                $shop_info  =$data['shop_info'];;
//                $this->es_data = $key;
                if($shop_info['shop_state']!=1){
                    throw new \RuntimeException("此商家不在上架状态，无需更新es", ErrorCode::SERVER_ERROR);
                }
                $this->es_data = [
                    'eid'=>intval($data['id']),
                    'es_key'=>$key['es_key'],
                    'es_type'=>$key['es_type'],
                    'name'=>$data['product_name'],
                    'key_word'=>$data['product_name'].implode('',$spec_key).implode('',array_column($sku_list,'sku_name')),
                    'desc'=>$data,
                    'min_price'=>doubleval($this->productService->get_best_price($data['id'],1)),
                    'max_price'=>doubleval($this->productService->get_best_price($data['id'],2)),
                    'sku_list'=>$sku_list,
                    'sales_actual'=>intval($data['sales_actual']),
                    'spec_key'=>$spec_key,
                    'shop_info'=>$shop_info,
                    'is_show'=>intval($data['is_show']),
                    'goods_type'=>intval($data['type']),
                    'is_illegal'=>intval($data['is_illegal']),
                    'check_status'=>$data['check_status'],
                ];
//                $this->sku_data($sku_list,$shop_info,$spec_key,$data);
            }else{
                throw new \RuntimeException("商品不存在", ErrorCode::SERVER_ERROR);
            }


        $old_data = $this->es_info(intval($data['id']),1,true);

            if($old_data){
//                        有旧数据则更新
                $this->updateById($old_data['0']['_id'],$this->es_data);
            }else{
                $this->insert($this->es_data);
            }
    }
    public function  shop_data($shop_id)   {
            $data = $this->shopService->getShopInfo(intval($shop_id));
            $key = $this->set_key($shop_id,4);
            if($data){
                if(is_object($data)){
                    $data =  $data->toArray();
                }
                $this->es_data = [
                    'eid'=>intval($data['id']),
                    'es_key'=>$key['es_key'],
                    'es_type'=>$key['es_type'],
                    'name'=>$data['shop_name'],
                    'key_word'=>$data['shop_name'].$data['shop_desc'].$data['business_scope'],
                    'desc'=>$data,
                    'down_shelf_reason'=>$data['down_shelf_reason'],
                    'address_info'=>$data['address_info'],
                    'link_name'=>$data['link_name'],
                    'lng'=>doubleval($data['lng']),
                    'lat'=>doubleval($data['lat']),
                    'food_sales_volume'=>$data['food_sales_volume'],
                    'shop_sales_volume'=>$data['shop_sales_volume'],
                    'food_state'=>$data['food_state'],
                    'food_switch'=>$data['food_switch'],
                    'shop_state'=>$data['shop_state'],
                ];
            }else{
                throw new \RuntimeException("商铺不存在", ErrorCode::SERVER_ERROR);
            }

            $old_data = $this->es_info(intval($data['id']),4,true);
            if($old_data){
//                        有旧数据则更新
                $this->updateById($old_data['0']['_id'],$this->es_data);
            }else{
                $this->insert($this->es_data);
            }
    }

    public function  sku_data($sku_list,$shop_info,$spec_key,$data)   {
        $sku_data = [];
            foreach ($sku_list as $key=>$value) {
                $sku_data[] = [
                    'data_id'=>$value['sku_id'],
                    'es_key'=>'SKU_'.$value['sku_id'],
                    'es_type'=> 'SKU',
                    'name'=>$value['sku_name'],
                    'key_word'=>$value['sku_name'].$data['product_name'].implode(',',$spec_key),
                    'desc'=>$value,
                    'min_price'=>doubleval($this->productService->get_best_price($data['id'],1)),
                    'max_price'=>doubleval($this->productService->get_best_price($data['id'],2)),
                    'sku_list'=>$sku_list,
                    'sales_actual'=>intval($data['sales_actual']),
                    'spec_key'=>$spec_key,
                    'shop_info'=>$shop_info,
                    'is_show'=>intval($data['is_show']),
                    'is_sell'=>intval($data['is_sell']),
                    'check_status'=>$data['check_status'],
                ];
            }
        if($sku_data){
            $this->batchCreateOrUpdate($sku_data);
        }
    }

//    删除单条数据
    public function deleteDoc($id,$type)
    {
        $old =  $this->es_info(intval($id),intval($type),true);
        if($old){
            $old =  $old[0];
        }else{
            return  false;
        }

        $del_where = [
            'id'=>$old['_id'],
            'index'=>$this->index,
        ];
       return $this->client->delete($del_where);
    }
}